package com.infore.statisticsAndAlarm.service.impl;

import java.util.ArrayList;
import java.util.Comparator;
import java.util.Date;
import java.util.HashMap;
import java.util.IntSummaryStatistics;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

import javax.servlet.http.HttpServletRequest;

import org.apache.commons.lang.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import com.infore.statisticsAndAlarm.constant.Constants;
import com.infore.statisticsAndAlarm.enums.ResultStatus;
import com.infore.statisticsAndAlarm.externalInterface.IDataReceivingService;
import com.infore.statisticsAndAlarm.externalInterface.IStieMangementService;
import com.infore.statisticsAndAlarm.service.TwoRateComparisonService;
import com.infore.statisticsAndAlarm.util.CookiesUtil;
import com.infore.statisticsAndAlarm.util.DateUtil;
import com.infore.statisticsAndAlarm.util.ObjectMapperUtil;
import com.infore.statisticsAndAlarm.util.ResultEntity;
import com.infore.statisticsAndAlarm.vo.ChartsVo;

@Service
public class TwoRateComparisonServiceImpl implements TwoRateComparisonService {

	@Autowired
	private IStieMangementService iStieMangementService;
	@Autowired
	private ObjectMapperUtil ObjectMapperUtil;
	@Autowired
	private IDataReceivingService iDataReceivingService;

	/** 多站点多因子站点mn时间段--分组得到数据 **/
	public List<Map<String, Object>> datasCenterMore(String type, String startTime, String endTime,
			List<String> mnList) {
		List<Map<String, Object>> dataResult = new ArrayList<Map<String, Object>>();// 小时天月数据结果集
		String stationMn = StringUtils.join(mnList, ",");
		// 查询单站点下因子code集合
		ResultEntity projectCodesEntity = iStieMangementService.queryProjectByStationMn(stationMn);
		List<String> projectCodes = ObjectMapperUtil.convertList(projectCodesEntity, String.class);// 站点下因子集合
		if (projectCodes == null || projectCodes.size() == 0) {
			return dataResult;
		}
		List<Map<String, Object>> dataResults = new ArrayList<Map<String, Object>>();
		if (projectCodes == null || mnList == null || projectCodes.size() == 0 || mnList.size() == 0) {
			return dataResults;
		}
		String codeString = StringUtils.join(projectCodes, ",");
		// 判断查询那钟类型的表
		if ("M".equals(type)) {// 分钟
		} else if ("S".equals(type)) {// 秒
		} else {// 查询小时表
			ResultEntity resultEntity = iDataReceivingService.audioMoreReport(stationMn, codeString, startTime,
					endTime);
			if (resultEntity.getCode() != 0) {
				return dataResults;
			}
			dataResults = ObjectMapperUtil.convertListMap(resultEntity);
		} 
		return dataResults;
	}

	/**
	 * 计算单个站点的数据上传率
	 * 
	 * @param mn
	 * @param dataResult
	 * @param startTime
	 * @param endTime
	 * @param frequnceRate
	 * @return
	 */
	public Map<String, Object> calculateRate(String mn, List<Map<String, Object>> dataResult, String startTime,
			String endTime, String frequnceRate) {
		if (dataResult == null || dataResult.size() == 0) {
			return null;
		}
		// 计算时间段内的时间长度
		Long rangevalue = 1L;
		Long start = DateUtil.stringToDate(startTime, DateUtil.DATE_FULL_STR).getTime();
		Long end = DateUtil.stringToDate(endTime, DateUtil.DATE_FULL_STR).getTime();
		Date date = new Date();
		if (end > date.getTime()) {
			end = date.getTime();
		}
		rangevalue = (end - start);
		// 判断数据发送频率
		Map<String, Object> result = new HashMap<String, Object>();
		Integer frequnce = 1000 * 60 * 60;// 默认一小时一条
		if (StringUtils.isNotBlank(frequnceRate)) {
			String frequnceType = frequnceRate.substring(frequnceRate.length() - 1);// 例如4H,截取最后一位单位
			Integer stationRate = Integer.parseInt(frequnceRate.substring(0, frequnceRate.length() - 1));// 截取单位下发送频率
			if ("M".equals(frequnceType)) {// 分钟
				frequnce = 1000 * 60 * stationRate;
			} else if ("S".equals(frequnceType)) {// 秒
				frequnce = 1000 * stationRate;
			} else if ("H".equals(frequnceType)) {
				frequnce = 1000 * 60 * 60 * stationRate;// 小时
			}
		}
		Long rateSize = rangevalue / frequnce;// 计算该时段长度内单因子应该有多少条数据
		// 计算站点下数据发送总数
		IntSummaryStatistics total = dataResult.stream()
				.collect(Collectors.summarizingInt(l -> Integer.parseInt(l.get("COUNT").toString())));
		Integer size = dataResult.size();// 因子数目
		Double rate = (total.getSum() * 1.0 / (rateSize * size)) * 100.0;
		rate = rate > 100.0 ? 100.0 : rate;
		result.put(mn, rate);
		return result;
	}

	/**
	 * 排序调用的方法
	 * 
	 * @param map
	 * @return
	 */
	private static Double comparingByRate(Map<String, Object> map) {
		return Double.parseDouble(map.get("rate").toString());
	}

	public ResultEntity uploadRateReports(String timeType, String startTime, String endTime, String queryCode,
			String queryType, HttpServletRequest request) {
		List<Map<String, Object>> list = new ArrayList<Map<String, Object>>();// 返回结果集
		List<Map<String, Object>> stationList = new ArrayList<Map<String, Object>>();// 站点信息集合
		String platfrom = CookiesUtil.getCookieValue(request, "platformId");
		String appCode = CookiesUtil.getCookieValue(request, "appCode");
		String userId = CookiesUtil.getCookieValue(request, "userId");
		String admin = CookiesUtil.getCookieValue(request, "admin");
		ResultEntity stationResultEntity = iStieMangementService.queryStationInfoByCodes(queryCode, queryType, userId,
				platfrom, appCode, admin);// 根据区域流域查询站点
		if (stationResultEntity.getCode() == 0) {
			stationList = ObjectMapperUtil.getMapList(stationResultEntity);
			Map<String, Object> stationInfo = new HashMap<String, Object>();// 保存站点编号和名称
			stationList.forEach(p -> {
				stationInfo.put(p.get("MN").toString(), p.get("STATIONNAME"));
			});
			// 按站点发送频率对站点分组
			Map<String, List<Map<String, Object>>> stationGroup = stationList.stream().collect(Collectors.groupingBy(
					l -> l.get("FREQUENCY").toString().substring(l.get("FREQUENCY").toString().length() - 1)));
			// 按照发送频率分组后的站点，得到数据并进行计算
			stationGroup.forEach((k, klist) -> {
				List<String> nmList = klist.stream().map(n -> n.get("MN").toString()).collect(Collectors.toList());
				List<Map<String, Object>> dataResult = new ArrayList<Map<String, Object>>();
				String type = k;
				dataResult = datasCenterMore(type, startTime, endTime, nmList);
				// 再根据mn号对站点进行分组
				Map<String, List<Map<String, Object>>> grouplist = dataResult.stream()
						.collect(Collectors.groupingBy(l -> l.get("MN").toString()));
				klist.forEach(t -> {
					// 封装数据
					String mn = t.get("MN").toString();
					Map<String, Object> singleRate = new HashMap<>();
					String frequence = t.get("FREQUENCY").toString();// 站点发送频率
					singleRate.put("mn", mn);
					singleRate.put("name", stationInfo.get(mn));
					Map<String, Object> result = calculateRate(mn, grouplist.get(mn), startTime, endTime, frequence);// 计算单站发送频率
					// 判断计算结果不能为空
					if (result != null && result.size() != 0) {
						if (result.keySet().contains(mn)) {
							Double rate = (Double) result.get(mn);
							singleRate.put("rate", String.format("%.2f", rate));
						} else {
							singleRate.put("rate", "0.0");
						}
					} else {
						singleRate.put("rate", "0.0");
					}
					list.add(singleRate);
				});
			});
		}
		// 按照上传率对站点进行排序
		List<Map<String, Object>> collect = list.stream()
				.sorted(Comparator.comparing(TwoRateComparisonServiceImpl::comparingByRate).reversed())
				.collect(Collectors.toList());
		Map<String, Object> message = new HashMap<String, Object>();
		String msg = startTime.substring(0, 10) + "至" + endTime.substring(0, 10) + "数据上传率第一名为：";
		if (collect != null && collect.size() > 0) {
			msg = msg + collect.get(0).get("rate") + "%";
		}
		message.put("message", msg);
		return new ResultEntity(ResultStatus.SUCCESS, Constants.QUERY_SUCCESS).setDataList(collect).setInfo(message);
	}

	public ResultEntity uploadRateBars(String timeType, String startTime, String endTime, String queryCode,
			String queryType, HttpServletRequest request) {
		// 结果集
		ChartsVo chartsVo = new ChartsVo();
		List<Map<String, Object>> series = new ArrayList<Map<String, Object>>();
		List<String> data = new ArrayList<String>();
		List<String> xAxis = new ArrayList<String>();
		List<Map<String, Object>> stationList = new ArrayList<Map<String, Object>>();// 站点信息集合
		String platfrom = CookiesUtil.getCookieValue(request, "platformId");
		String appCode = CookiesUtil.getCookieValue(request, "appCode");
		String userId = CookiesUtil.getCookieValue(request, "userId");
		String admin = CookiesUtil.getCookieValue(request, "admin");
		ResultEntity stationResultEntity = iStieMangementService.queryStationInfoByCodes(queryCode, queryType, userId,
				platfrom, appCode, admin);// 根据区域流域查询站点
		if (stationResultEntity.getCode() == 0) {
			stationList = ObjectMapperUtil.getMapList(stationResultEntity);
			Map<String, Object> stationInfo = new HashMap<String, Object>();// 保存站点编号和名称
			stationList.forEach(p -> {
				stationInfo.put(p.get("MN").toString(), p.get("STATIONNAME"));
			});
			// 按站点发送频率对站点分组
			Map<String, List<Map<String, Object>>> stationGroup = stationList.stream().collect(Collectors.groupingBy(
					l -> l.get("FREQUENCY").toString().substring(l.get("FREQUENCY").toString().length() - 1)));
			// 按照发送频率分组后的站点，得到数据并进行计算
			stationGroup.forEach((k, klist) -> {
				List<String> nmList = klist.stream().map(n -> n.get("MN").toString()).collect(Collectors.toList());
				List<Map<String, Object>> dataResult = new ArrayList<Map<String, Object>>();
				String type = k;
				dataResult = datasCenterMore(type, startTime, endTime, nmList);
				// 再根据mn号对站点进行分组
				Map<String, List<Map<String, Object>>> grouplist = dataResult.stream()
						.collect(Collectors.groupingBy(l -> l.get("MN").toString()));
				klist.forEach(t -> {
					// 封装数据
					String mn = t.get("MN").toString();
					String frequence = t.get("FREQUENCY").toString();// 站点发送频率
					xAxis.add(stationInfo.get(mn).toString());
					Map<String, Object> result = calculateRate(mn, grouplist.get(mn), startTime, endTime, frequence);// 计算单站发送频率
					// 判断计算结果不能为空
					if (result != null && result.size() != 0) {
						if (result.keySet().contains(mn)) {
							Double rate = (Double) result.get(mn);
							data.add(String.format("%.2f", rate));
						} else {
							data.add("0.0");
						}
					} else {
						data.add("0.0");
					}
				});
			});
		}
		Map<String, Object> seriesMap = new HashMap<String, Object>();
		seriesMap.put("data", data);
		series.add(seriesMap);
		chartsVo.setxAxis(xAxis);
		chartsVo.setSeries(series);
		if (series == null || series.size() == 0) {
			return new ResultEntity(ResultStatus.SUCCESS, Constants.QUERY_SUCCESS);
		}
		return new ResultEntity(ResultStatus.SUCCESS, Constants.QUERY_SUCCESS).setInfo(chartsVo);
	}

	// 根据发送频率单位对站点进行分组-》查询分组后的数据-》根据站点mn号分组---计算每个站点的发送频率
	public ResultEntity uploadRateYoY(String timeType, String startTime, String endTime, String queryCode,
			String queryType, String compareType, HttpServletRequest request) {
		// 结果集
		ChartsVo chartsVo = new ChartsVo();
		List<Map<String, Object>> series = new ArrayList<Map<String, Object>>();
		List<String> data = new ArrayList<String>();
		List<String> dataCompare = new ArrayList<String>();
		List<String> changeRate = new ArrayList<String>();
		List<String> xAxis = new ArrayList<String>();
		// 查询数据
		// 区域流域下站点信息
		List<Map<String, Object>> stationList = new ArrayList<Map<String, Object>>();// 站点信息集合
		String platfrom = CookiesUtil.getCookieValue(request, "platformId");
		String appCode = CookiesUtil.getCookieValue(request, "appCode");
		String userId = CookiesUtil.getCookieValue(request, "userId");
		String admin = CookiesUtil.getCookieValue(request, "admin");
		ResultEntity stationResultEntity = iStieMangementService.queryStationInfoByCodes(queryCode, queryType, userId,
				platfrom, appCode, admin);// 根据区域流域查询站点
		if (stationResultEntity.getCode() == 0) {
			stationList = ObjectMapperUtil.getMapList(stationResultEntity);
			Map<String, Object> stationInfo = new HashMap<String, Object>();// 保存站点编号和名称
			stationList.forEach(p -> {
				stationInfo.put(p.get("MN").toString(), p.get("STATIONNAME"));
			});
			// 按站点发送频率单位对站点分组
			Map<String, List<Map<String, Object>>> stationGroup = stationList.stream().collect(Collectors.groupingBy(
					l -> l.get("FREQUENCY").toString().substring(l.get("FREQUENCY").toString().length() - 1)));
			// 按照发送频率分组后的站点，得到数据并进行计算
			stationGroup.forEach((k, klist) -> {
				String compareSatrt = "";// 对比开始时间
				String compareEnd = "";// 对比结束时间
				// 如果是同比，则年份减一，否则环比月份减一
				if ("H".equals(compareType)) {
					compareSatrt = DateUtil.addYear(startTime, -1, DateUtil.DATE_FULL_STR);
					compareEnd = DateUtil.addYear(endTime, -1, DateUtil.DATE_FULL_STR);
				} else {
					compareSatrt = DateUtil.addMonth(startTime, -1, DateUtil.DATE_FULL_STR);
					compareEnd = DateUtil.addMonth(endTime, -1, DateUtil.DATE_FULL_STR);
				}
				// 查询发送频率单位相同的站点
				List<String> nmList = klist.stream().map(n -> n.get("MN").toString()).collect(Collectors.toList());
				List<Map<String, Object>> dataResult = new ArrayList<Map<String, Object>>();
				List<Map<String, Object>> dataResultCompare = new ArrayList<Map<String, Object>>();
				String type = k;
				dataResult = datasCenterMore(type, startTime, endTime, nmList);
				dataResultCompare = datasCenterMore(type, compareSatrt, compareEnd, nmList);
				// 再根据mn号对站点进行分组
				Map<String, List<Map<String, Object>>> grouplist = dataResult.stream()
						.collect(Collectors.groupingBy(l -> l.get("MN").toString()));
				Map<String, List<Map<String, Object>>> grouplistCompare = dataResultCompare.stream()
						.collect(Collectors.groupingBy(com -> com.get("MN").toString()));
				klist.forEach(t -> {
					String compareSatrt1 = "";
					String compareEnd1 = "";
					if ("H".equals(compareType)) {
						compareSatrt1 = DateUtil.addYear(startTime, -1, DateUtil.DATE_FULL_STR);
						compareEnd1 = DateUtil.addYear(endTime, -1, DateUtil.DATE_FULL_STR);
					} else {
						compareSatrt1 = DateUtil.addMonth(startTime, -1, DateUtil.DATE_FULL_STR);
						compareEnd1 = DateUtil.addMonth(endTime, -1, DateUtil.DATE_FULL_STR);
					}
					// 封装数据
					String mn = t.get("MN").toString();
					String frequence = t.get("FREQUENCY").toString();// 站点发送频率
					xAxis.add(stationInfo.get(mn).toString());
					List<Map<String, Object>> dd = grouplist.get(mn) == null ? null : grouplist.get(mn);
					List<Map<String, Object>> dd1 = grouplistCompare.get(mn) == null ? null : grouplistCompare.get(mn);
					// 计算每个站点的发送频率
					Map<String, Object> result = calculateRate(mn, dd, startTime, endTime, frequence);// 计算单站发送频率
					Map<String, Object> resultCompare = calculateRate(mn, dd1, compareSatrt1, compareEnd1, frequence);// 计算单站发送频率
					// 判断计算结果不能为空
					if (result != null && result.size() != 0) {
						if (result.keySet().contains(mn)) {
							Double rate = (Double) result.get(mn);
							data.add(String.format("%.2f", rate));
						} else {
							data.add("0.0");
						}
					} else {
						data.add("0.0");
					}
					if (resultCompare != null && resultCompare.size() != 0) {
						if (resultCompare.keySet().contains(mn)) {
							Double rate1 = (Double) resultCompare.get(mn);
							dataCompare.add(String.format("%.2f", rate1));
						} else {
							dataCompare.add("0.0");
						}
					} else {
						dataCompare.add("0.0");
					}
					// 计算发送频率的增长率
					Integer index = xAxis.size() - 1;
					if (data.get(index) != null || dataCompare.get(index) != null) {
						Double rateNative = Double.parseDouble(data.get(index));
						Double rateCompare = Double.parseDouble(dataCompare.get(index));
						if (rateCompare == 0 || rateCompare == null) {
							changeRate.add(null);
						} else {
							Double changeRates = (rateNative - rateCompare) / Math.abs(rateCompare) * 100;
							if (rateNative - rateCompare < 0) {
								changeRates = changeRates * -1;
								changeRate.add("-" + String.format("%.2f", changeRates));
							} else {
								changeRate.add(String.format("%.2f", changeRates));
							}
						}
					} else {
						changeRate.add(null);
					}
				});
			});
		}
		// 设置返回时间格式
		String compTime = "";// 对比开始时间
		String startTime11 = "";
		// 如果是同比，则年份减一，否则环比月份减一
		if ("H".equals(compareType)) {
			compTime = DateUtil.addYear(startTime, -1, DateUtil.DATE_FULL_STR);
		} else {
			compTime = DateUtil.addMonth(startTime, -1, DateUtil.DATE_FULL_STR);
		}
		if ("day".equals(timeType)) {
			startTime11 = startTime.substring(0, 10);
			compTime = compTime.substring(0, 10);
		} else if ("month".equals(timeType)) {
			startTime11 = startTime.substring(0, 7);
			compTime = compTime.substring(0, 7);
		} else {
			startTime11 = startTime.substring(0, 4);
			compTime = compTime.substring(0, 4);
		}
		Map<String, Object> seriesData = new HashMap<String, Object>();
		Map<String, Object> seriesComnpare = new HashMap<String, Object>();
		Map<String, Object> seriesChange = new HashMap<String, Object>();
		seriesData.put("name", startTime11);
		seriesData.put("data", data);
		seriesComnpare.put("name", compTime);
		seriesComnpare.put("data", dataCompare);
		seriesChange.put("name", "增长率");
		seriesChange.put("data", changeRate);
		series.add(seriesData);
		series.add(seriesComnpare);
		series.add(seriesChange);
		chartsVo.setxAxis(xAxis);
		chartsVo.setSeries(series);
		if (series == null || series.size() == 0 || xAxis == null || xAxis.size() == 0) {
			return new ResultEntity(ResultStatus.SUCCESS, Constants.QUERY_SUCCESS);
		}
		return new ResultEntity(ResultStatus.SUCCESS, Constants.QUERY_SUCCESS).setInfo(chartsVo);
	}

	@Override
	public ResultEntity dataValidUploadRate(String type, String time, String stationMn, String sTime, String eTime) {
		return null;
	}

}
